(function(root){
    const Jquery = function() {
        return new Jquery.prototype.init()
    }
    Jquery.fn = Jquery.prototype = {
        init: function() {

        },
        extend: function() {

        }
    }

    Jquery.fn.extend = Jquery.extend = function(...args) {
        let target = args[0],
            length = args.length,
            deep = false,
            opt,
            name,
            copy,
            copyIsArr,
            src,
            clone,
            i = 1;
        if (typeof target === 'boolean') {
            deep = target
            target = args[1]
            i = 2
        }
        if (typeof target !== 'object') {
            target = {}
        }
        /* 此时this指向可根据调用方式，
            $.extend()为jquery扩展属性方法。
            $.fn.extend为jquery实例
        */
        if (length === i) {
            target = this
            i--
        }

        for(; i < length; i++) {
            if ((opt = args[i]) !== null) {
                for(name in opt) {
                    copy = opt[name],
                    src = target[name]
                    if (deep && (Jquery.isPlainObject(copy) || (copyIsArr = Jquery.isArray(copy)))) {
                        if (copyIsArr) {
                            clone = src && Jquery.isArray(src) ? src : [] 
                        } else {
                            clone = src && Jquery.isPlainObject(src) ? src : {} 
                        }
                        target[name] = Jquery.extend(deep, clone, copy)
                    } else if(copy !== undefined) {
                        target[name] = copy
                    }
                }
            }
        }
        return target
    }
    Jquery.extend({
        isPlainObject: (val) => toString.call(val) === '[object Object]',
        isArray: (val) => toString.call(val) === 'object Array',
        isBoolean: (val) => toString.call(val) === 'object Boolean'
    })
    Jquery.fn.init.prototype = Jquery.fn
    root.$ = root.Jquery = Jquery
})(this)